package adapletplugin.editors;

import objects.Interface;

import org.eclipse.jface.viewers.IStructuredContentProvider;
import org.eclipse.jface.viewers.ITableLabelProvider;
import org.eclipse.jface.viewers.LabelProvider;
import org.eclipse.jface.viewers.TableViewer;
import org.eclipse.jface.viewers.Viewer;
import org.eclipse.jface.window.Window;
import org.eclipse.swt.SWT;
import org.eclipse.swt.custom.ScrolledComposite;
import org.eclipse.swt.events.ModifyEvent;
import org.eclipse.swt.events.ModifyListener;
import org.eclipse.swt.events.SelectionAdapter;
import org.eclipse.swt.events.SelectionEvent;
import org.eclipse.swt.events.SelectionListener;
import org.eclipse.swt.graphics.Image;
import org.eclipse.swt.layout.GridData;
import org.eclipse.swt.layout.GridLayout;
import org.eclipse.swt.widgets.Button;
import org.eclipse.swt.widgets.Composite;
import org.eclipse.swt.widgets.Shell;
import org.eclipse.swt.widgets.TableColumn;
import org.eclipse.swt.widgets.Text;
import org.eclipse.ui.PlatformUI;
import org.eclipse.ui.forms.widgets.FormToolkit;

import adapletplugin.dialogs.NewAttributeDialog;

public class InterfaceEditor extends AbstractSubEditor
{
	private Text fInterfaceNameText;
	private Text fTableText;
	private Text fBaseObjectText;
	private Text fBaseObjColText;

	private Interface interFocus;

	// TABLE for attributes
	private Button fNewAttributeButton;
	private TableViewer fAttributeTable;

	public InterfaceEditor(ScrolledComposite composite, FormToolkit toolkit, MapFileEditor parentEditor)
	{
		super(composite, toolkit, parentEditor);
	}

	@Override
	protected void create()
	{
		Composite row = fToolkit.createComposite(fSubComposite);
		row.setLayout(new GridLayout(2, false));
		row.setLayoutData(new GridData(SWT.FILL, SWT.FILL, true, false));

		fToolkit.createLabel(row, "Interface Name:");
		fInterfaceNameText = fToolkit.createText(row, "", SWT.BORDER | SWT.READ_ONLY);
		fInterfaceNameText.setLayoutData(new GridData(SWT.FILL, SWT.FILL, true, false));
		fInterfaceNameText.addModifyListener(createModifyListener_Name());

		fToolkit.createLabel(row, "Table Name:");
		fTableText = fToolkit.createText(row, "", SWT.BORDER);
		fTableText.setLayoutData(new GridData(SWT.FILL, SWT.FILL, true, false));
		fTableText.addModifyListener(createModifyListener_Table());

		fToolkit.createLabel(row, "Base Object:");
		fBaseObjectText = fToolkit.createText(row, "", SWT.BORDER);
		fBaseObjectText.setLayoutData(new GridData(SWT.FILL, SWT.FILL, true, false));
		fBaseObjectText.addModifyListener(createModifyListener_Base());

		fToolkit.createLabel(row, "Base Object Column:");
		fBaseObjColText = fToolkit.createText(row, "", SWT.BORDER);
		fBaseObjColText.setLayoutData(new GridData(SWT.FILL, SWT.FILL, true, false));
		fBaseObjColText.addModifyListener(createModifyListener_BaseCol());

		// TODO attributes
		fNewAttributeButton = fToolkit.createButton(fSubComposite, "Add Attribute", SWT.PUSH);
		fNewAttributeButton.setLayoutData(new GridData(SWT.RIGHT, SWT.FILL, false, false));
		fNewAttributeButton.addSelectionListener(createNewAttributeListener());

		fAttributeTable = new TableViewer(fSubComposite, SWT.BORDER | SWT.V_SCROLL | SWT.SINGLE | SWT.FULL_SELECTION);
		fAttributeTable.getTable().setLayoutData(new GridData(SWT.FILL, SWT.FILL, true, true));
		fAttributeTable.setContentProvider(new AttributeTableContentProvider());
		fAttributeTable.setLabelProvider(new AttributeTableLabelProvider());

		TableColumn col = new TableColumn(fAttributeTable.getTable(), SWT.LEFT);
		col.setMoveable(false);
		col.setResizable(true);
		col.setText("Attribute");
		col.setWidth(100);

		col = new TableColumn(fAttributeTable.getTable(), SWT.RIGHT);
		col.setMoveable(false);
		col.setResizable(true);
		col.setText("Table Column");
		col.setWidth(100);

		fAttributeTable.getTable().setHeaderVisible(true);

		fAttributeTable.setInput(new AttributeTableInput(interFocus));

	}

	private SelectionListener createNewAttributeListener()
	{
		return new SelectionAdapter() {

			@Override
			public void widgetSelected(SelectionEvent e)
			{
				Shell shell = PlatformUI.getWorkbench().getActiveWorkbenchWindow().getShell();

				NewAttributeDialog dialog = new NewAttributeDialog(shell);

				dialog.create();
				dialog.open();

				if (dialog.getReturnCode() == Window.OK)
				{
					interFocus.addAttribute(dialog.getAttribute(), dialog.getColumn());

					fAttributeTable.refresh();
					fEditor.refresh();
				}
			}
		};
	}

	private ModifyListener createModifyListener_BaseCol()
	{
		return new ModifyListener() {

			@Override
			public void modifyText(ModifyEvent e)
			{
				interFocus.setBaseObjectColumn(fBaseObjColText.getText());
				fEditor.refresh();
			}
		};
	}

	private ModifyListener createModifyListener_Base()
	{
		return new ModifyListener() {

			@Override
			public void modifyText(ModifyEvent e)
			{
				interFocus.setBaseObject(fBaseObjectText.getText());
				fEditor.refresh();
			}
		};
	}

	private ModifyListener createModifyListener_Table()
	{
		return new ModifyListener() {

			@Override
			public void modifyText(ModifyEvent e)
			{
				interFocus.setTableName(fTableText.getText());
				fEditor.refresh();
			}
		};
	}

	private ModifyListener createModifyListener_Name()
	{
		return new ModifyListener() {

			@Override
			public void modifyText(ModifyEvent e)
			{
				interFocus.setInterfaceName(fInterfaceNameText.getText());
				fEditor.refresh();
			}
		};
	}

	@Override
	protected void updateFields()
	{
		interFocus = (Interface) fFocusObject;

		fInterfaceNameText.setText(interFocus.getInterfaceName());
		fTableText.setText(interFocus.getTableName());
		fBaseObjectText.setText(interFocus.getBaseObject());
		fBaseObjColText.setText(interFocus.getBaseObjectColumn());

		fAttributeTable.setInput(new AttributeTableInput(interFocus));

	}

	private class AttributeTableContentProvider implements IStructuredContentProvider
	{

		@Override
		public void dispose()
		{

		}

		@Override
		public void inputChanged(Viewer viewer, Object oldInput, Object newInput)
		{

		}

		@Override
		public Object[] getElements(Object inputElement)
		{
			return ((AttributeTableInput) inputElement).getData();
		}

	}

	private class AttributeTableLabelProvider extends LabelProvider implements ITableLabelProvider
	{

		@Override
		public Image getColumnImage(Object element, int columnIndex)
		{
			return null;
		}

		@Override
		public String getColumnText(Object element, int columnIndex)
		{
			if (columnIndex == 0)
			{
				return (String) element;
			}
			else if (columnIndex == 1)
			{
				return interFocus.getAttributeColumn((String) element);
			}
			else
			{
				return "INVALID COLUMN";
			}
		}

	}

	private class AttributeTableInput
	{
		private Interface fInput;

		public AttributeTableInput(Interface inter)
		{
			fInput = inter;
		}

		public String[] getData()
		{
			if (fInput == null)
			{
				return new String[0];
			}
			return fInput.getAttributeNames();
		}
	}

}
